<?php


namespace app\cms\oauth\controller;


use app\community\boot\oauth2\oauthBoot;
use iflow\Container\implement\annotation\tools\data\Inject;
use iflow\Response;
use iflow\Router\Controller;
use iflow\Router\implement\Request\{ GetMapping, PostMapping };
use League\OAuth2\Server\Exception\OAuthServerException;
use Psr\Http\Message\ResponseInterface;

#[Controller('%oauth2%/authorization')]
class authorizationCodeGrantController
{

    #[Inject]
    public oauthBoot $oauthBoot;

    /**
     * GET Authorization code
     * @return ResponseInterface|Response
     */
    #[GetMapping]
    public function code(): ResponseInterface|Response
    {
        try {
            $this->oauthBoot
                -> enableGrantType()
                -> validateAuthorizationRequest()
                -> getAuthorizationRequest()
                -> setAuthorizationApproved(true);

            return $this->oauthBoot
                        -> getOauthServer()
                        -> completeAuthorizationRequest(
                            $this->oauthBoot -> getAuthorizationRequest(),
                            response() -> getResponsePsr7()
                        );
        } catch (OAuthServerException | \Exception $exception) {
            return message() -> server_error($exception -> getCode(), $exception -> getMessage());
        }
    }


    /**
     * GetAccessToken By AuthorizationCode
     * @return ResponseInterface|Response
     */
    #[PostMapping]
    public function accessToken(): ResponseInterface|Response {
        try {
            return $this->oauthBoot
                -> enableGrantType()
                -> getOauthServer()
                -> respondToAccessTokenRequest(
                    request() -> getServerRequestPsr7(),
                    response() -> getResponsePsr7()
                );
        } catch (OAuthServerException | \Exception $exception) {
            return message() -> server_error($exception -> getCode(), $exception -> getMessage());
        }
    }
}